

#ifndef	_LINKED_QUEUE_2_H_
#define	_LINKED_QUEUE_2_H_

#include "LinkedList2Node.hpp"

template <typename T> class LinkedQueue2{
public:
	LinkedList2Node<T> *head, *end;

	CALLCONV LinkedQueue2(LinkedList2Node<T> *firstNode = (LinkedList2Node<T>*)0){
		head = end = firstNode;
	}
	
	inline bool isEmpty(){
		if(this == (LinkedQueue2*)0) return true;
		if(head == (LinkedList2Node<T>*)0) return true;
		return false;
	}
	
	CALLCONV unsigned getSize(){
		if(this == (LinkedQueue2*)0) return 0;
		unsigned size = 0;
		for(LinkedList2Node<T> *temp = head;
			temp != (LinkedList2Node<T>*)0;
			temp = temp->next) size++;
		return size;
	}
	
	CALLCONV unsigned indexOf(T element){
		if(this == (LinkedQueue2*)0) return ~(unsigned)0;
		unsigned index = 0;
		for(LinkedList2Node<T> *temp = head;
				temp != (LinkedList2Node<T>*)0;
				temp = temp->next, index++)
			if(temp->key == element) return index;
		return ~(unsigned)0;
	}
	
	CALLCONV bool addNodeToFirst(LinkedList2Node<T> *node){
		if(this == (LinkedQueue2*)0) return false;
		if(node == (LinkedList2Node<T>*)0) return false;
		if((node->next = head) != (LinkedList2Node<T>*)0) head->prev = node;
		head = node;
		if(end == (LinkedList2Node<T>*)0) end = node;
		return true;
	}
	
	CALLCONV bool addNodeToLast(LinkedList2Node<T> *node){
		if(this == (LinkedQueue2*)0) return false;
		if(node == (LinkedList2Node<T>*)0) return false;
		if((node->prev = end) != (LinkedList2Node<T>*)0) end->next = node;
		end = node;
		if(head == (LinkedList2Node<T>*)0) head = node;
		return true;
	}
	
	CALLCONV bool removeFirstNode(LinkedList2Node<T> **pnode){
		if(this == (LinkedQueue2*)0) return false;
		if(head == (LinkedList2Node<T>*)0) return false;
		if(pnode != (LinkedList2Node<T>**)0) *pnode = head;
		LinkedList2Node<T> *temp = head;
		if((head = head->next) == (LinkedList2Node<T>*)0)
			end = (LinkedList2Node<T>*)0;
		else head->prev = (LinkedList2Node<T>*)0;
		return true;
	}
	
	CALLCONV bool removeLastNode(LinkedList2Node<T> **pnode){
		if(this == (LinkedQueue2*)0) return false;
		if(head == (LinkedList2Node<T>*)0) return false;
		if(pnode != (LinkedList2Node<T>**)0) *pnode = end;
		LinkedList2Node<T> *temp = end;
		if((end = end->prev) == (LinkedList2Node<T>*)0)
			head = (LinkedList2Node<T>*)0;
		else end->next = (LinkedList2Node<T>*)0;
		return true;
	}
	
	
}; // class LinkedQueue2<T>

#endif	// _LINKED_QUEUE_2_H_
